<template>
  <div class="container-publish">
    <el-card>
      <div slot="header">
        <my-bread>{{$route.query.id?'修改文章':'发布文章'}}</my-bread>
      </div>
      <!-- 表单 -->
      <el-form ref="articleForm" :model="aritcleForm" :rules="articleRules" label-width="120px">
        <!-- 标题 -->
        <el-form-item label="标题" prop="title">
          <el-input v-model="articleForm.title" placeholder="请输入标题" style="width:400px"></el-input>
        </el-form-item>
        <!-- 内容:富文本 -->
        <el-form-item label="内容" prop="content">
          <quill-editor @blur="checkContent" v-model="articleForm.content" :options="editorOption"></quill-editor>
        </el-form-item>
        <!-- 封面 -->
        <el-form-item label="封面" prop="cover">
          <el-radio-group @change="articleForm.cover.images=[]" v-model="articleForm.cover.type">
            <el-radio :label="1">单图</el-radio>
            <el-radio :label="3">三图</el-radio>
            <el-radio :label="0">无图</el-radio>
            <el-radio :label="-1">自动</el-radio>
          </el-radio-group>
          <div style="height:160px" v-if="articleForm.cover.type===1">
            <my-image v-model="articleForm.cover.images[0]"></my-image>
          </div>
          <div style="height:160px" v-if="articleForm.cover.type===3">
            <my-image v-for="i in 3" :key="i" v-model="articleForm.cover.images[i-1]"></my-image>
          </div>
        </el-form-item>
        <!-- 频道 -->
        <el-form-item label="频道" prop="channel_id">
          <my-channel v-model="articleForm.channel_id"></my-channel>
        </el-form-item>
        <el-form-item v-if="$route.query.id">
          <el-button @click="editArticle" type="success">修改文章</el-button>
        </el-form-item>
        <el-form-item v-else>
          <el-button type="primary" @click="addArticle(false)">发布文章</el-button>
          <el-button @click="addArticle(true)">存为草稿</el-button>
        </el-form-item>
      </el-form>
    </el-card>
  </div>
</template>

<script>
// 富文本配置
import "quill/dist/quill.core.css";
import "quill/dist/quill.snow.css";
import "quill/dist/quill.bubble.css";
// 组件配置
import { quillEditor } from "vue-quill-editor";

export default {
  name: "publish-page",
  // 富文本组件注册
  components: { quillEditor },
  data() {
    // 自定义校验
    const checkCover = (rule, value, callback) => {
      // 1张图
      if (value.type === 1) {
        if (!value.images[0]) {
          return callback(new Error("请选择封面图"));
        }
      }
      // 3张图
      if (value.type === 3) {
        if (!value.images[0] || !value.images[1] || !value.images[2]) {
          return callback(new Error("请选择3张封面图"));
        }
      }
      // 无图/自定义
      callback();
    };
    return {
      // 文章校验规则对象
      articleRules: {
        // 标题
        title: [
          { required: true, message: "请输入标题", trigger: "blur" },
          { min: 5, max: 30, message: "文章标题5-30个字符", trigger: "blur" }
        ],
        // 富文本不是element的表单元素组件，富文本的失去焦点监听不到,无法自动触发校验
        // 自定义监听富文本的失去焦点事件，在触发的时候手动去触发当前表单项的校验
        content: [{ required: true, message: "请输入内容", trigger: "blur" }],
        // cover对象需要自定义校验,用watch监听cover里面数据的变化
        cover: [{ validator: checkCover, trigger: "blur" }],
        // 频道校验,el-select组件触发的条件可以改成change
        channel_id: [
          { required: true, message: "请选择频道", trigger: "change" }
        ]
      },
      // 发布文章表单数据对象
      articleForm: {
        // 文章标题
        title: null,
        cover: {
          // 封面类型
          type: 1,
          // 图片数据
          images: []
        },
        // 频道id
        channel_id: null,
        // 文章内容
        content: null
      },
      // 富文本配置工具栏配置
      editorOption: {
        placeholder: "请输入内容",
        modules: {
          toolbar: [
            ["bold", "italic", "underline", "strike"],
            ["blockquote", "code-block"],
            [{ header: 1 }, { header: 2 }],
            [{ list: "ordered" }, { list: "bullet" }],
            [{ indent: "-1" }, { indent: "+1" }],
            ["image"]
          ]
        }
      }
    };
  },
  // 监听
  watch: {
    // articleForm.cover对象里面数据的变化触发这个函数
    "articleForm.cover": {
      // 数据变化时执行的处理函数
      handler() {
        // setTimeout(() => {
        //   this.$refs.articleForm.validateField("cover");
        // }, 0);
        this.$nextTick(() => {
          this.$refs.articleForm.validateField("cover");
        });
      },
      // 深度监听
      deep: true
    },
    // 地址栏id变化触发
    "$route.query.id": function() {
      if (this.$route.query.id) {
        // 填充表单
        this.getArticle();
      } else {
        // 重置表单
        this.articleForm = {
          title: null,
          cover: {
            type: 1,
            images: []
          },
          channel_id: null,
          content: null
        };
        // 清除校验效果
        // setTimeout() 中的函数比 $nextTick() 中的函数晚执行
        // this.$nextTick(() => {
        //   this.$refs.articleForm.resetFields();
        // });
        setTimeout(() => {
          this.$refs.articleForm.clearValidate(["cover", "channel_id"]);
        }, 0);
      }
    }
  },
  created() {
    // 触发created
    // 1. 从内容管理点击编辑，跳转到组件
    // 2. 点击发布文章，跳转到组件
    if (this.$route.query.id) {
      // 编辑文章场景
      this.getArticle();
    }
  },
  methods: {
    // 修改文章
    editArticle() {
      this.$refs.articleForm.validate(async valid => {
        try {
          // 发送修改请求
          await this.$http({
            method: "put",
            url: `/articles/${this.$route.query.id}`,
            // ?后键值对传参
            params: { draft: false },
            // 请求体传参
            data: this.articleForm
          });
          // 已经修改成功
          this.$message.success("修改文章成功");
          // 跳转内容管理
          this.$router.push("/article");
        } catch (e) {
          // 失败
          this.$message.error("修改文章失败");
        }
      });
    },
    // 获取文章
    async getArticle() {
      const {
        data: { data }
      } = await this.$http.get("/articles/" + this.$route.query.id);
      // 把数据填充到表单
      this.articleForm = data;
    },
    // 富文本校验
    checkContent() {
      this.$refs.articleForm.validateField("content");
    },
    // 发布文章
    addArticle(draft) {
      // 整体表单校验
      this.$refs.articleForm.validate(async valid => {
        if (valid) {
          try {
            await this.$http.post(`/articles?draft=${draft}`, this.articleForm);
            this.$message.success(draft ? "存入草稿成功" : "发布成功");
            // 成功后跳转
            this.$router.push("/article");
          } catch (e) {
            // 失败提示错误
            this.$message.error(draft ? "存入草稿成功" : "发布失败");
          }
        }
      });
    }
  }
};
</script>

<style scoped lang="less">
// 样式穿透,把样式放进全局样式
// /deep/样式在其他组件下的标签也生效vue-cli支持
/deep/ .ql-toolbar.ql-snow {
  padding: 0 8px;
}
/deep/ .ql-editor {
  height: 250px;
}
</style>